import datetime
import string
import traceback
from multiprocessing import Pool

import redis
import lxml.html
import json
import asyncio
import time
import random
import logging
import sys
import os

import pymongo
from faker import Faker
import base64
from Crypto.PublicKey import RSA
from Crypto.Cipher import PKCS1_v1_5
from io import BytesIO
from PIL import Image
import requests

from cmcc_10086 import login


# from baseHandler import init_logger

def get_ts():
    return str(time.time()).replace('.', '')[:13]


def decrypt(key, ciphertext):
    # key = RSA.importKey(pri)

    cipher = PKCS1_v1_5.new(key)
    _message = cipher.encrypt(ciphertext)
    return base64.b64encode(_message).decode()


def get_code(content):
    # headers = {"Authorization": "APPCODE 370107e384e1409b9af32352c20e6100"}
    # data = {
    #     'v_pic': base64.b64encode(content).decode(),
    #     'v_type': 'ne6'
    # }
    # # print(data)
    #
    # url = 'http://yzm.cqjianjiao.com/yzm'
    # rsp = requests.post(url, data=data, headers=headers)
    # rsp_obj = rsp.text
    # rsp_obj = json.loads(rsp_obj)
    # if rsp_obj['errCode'] == 0:
    #     # v_code = rsp_obj['v_code']
    #     # with open('/app/log/captcha/' + v_code + '.png', 'wb') as f:
    #     #     f.write(content)
    #     return rsp_obj['v_code']
    # else:
    #     return None
    data = {
        'image_base64': base64.b64encode(content).decode(),
        'app_id': '379809080',
        # 'image_code': '0000'
    }
    # async with aiohttp.ClientSession() as session:
    url = 'https://nmd-ai.juxinli.com/ocr_captcha'
    rsp = requests.post(url, json=data)
    rsp_obj =  rsp.json()
    #rsp_obj = json.loads(rsp_obj)
    print(rsp_obj)
    if rsp_obj['errorcode'] == 0:
        v_code = rsp_obj['string']
        return v_code

    return None


class REG10086:
    def __init__(self, email, raw_password, redis):
        key = "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsgDq4OqxuEisnk2F0EJFmw4xKa5IrcqEYHvqxPs2CHEg2kolhfWA2SjNuGAHxyDDE5MLtOvzuXjBx/5YJtc9zj2xR/0moesS+Vi/xtG1tkVaTCba+TV+Y5C61iyr3FGqr+KOD4/XECu0Xky1W9ZmmaFADmZi7+6gO9wjgVpU9aLcBcw/loHOeJrCqjp7pA98hRJRY+MML8MK15mnC4ebooOva+mJlstW6t/1lghR8WNV8cocxgcHHuXBxgns2MlACQbSdJ8c6Z3RQeRZBzyjfey6JCCfbEKouVrWIUuPphBL3OANfgp0B+QG31bapvePTfXU48TYK0M5kE+8LgbbWQIDAQAB"
        pub = RSA.importKey(base64.b64decode(key))
        self.login_url = 'https://login.10086.cn/registersubmit.htm'
        # raw_password = gen_nonce_str(N=8)
        password = decrypt(pub, raw_password.encode())
        newpassword = decrypt(pub, raw_password.encode())
        self.data = {
            'loginName': email,
            'userPassword': password,
            'newPasswordRepeat': newpassword,
            'inputCode': '',
            'channelId': '',
            'timestamp': get_ts()
        }
        self.sess = requests.Session()
        self.redis = redis

    def proxy(self):
        proxys = redis.smembers('un_proxy')
        if proxys:
            proxy = random.choice(list(i.decode() for i in proxys if i))
            conn = proxy or None
        else:
            conn = None
        return {"http": conn}

    def reg(self):
        headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36',
            'Host': 'login.10086.cn',
            'Referer': 'https://login.10086.cn/html/register/register.html'

        }
        # self.sess.get('https://login.10086.cn/html/register/register.html', proxies=self.proxy)
        self.sess.get('https://login.10086.cn/html/register/register.html', headers=headers)
        for i in range(6):
            rsp = self.sess.get('https://login.10086.cn/captchazh.htm?type=05&timestamp=' + get_ts(), headers=headers)
            text = rsp.content
            captcha = get_code(text)
            self.data['inputCode'] = captcha
            rsp = self.sess.post(self.login_url, data=self.data, headers=headers)
            content = rsp.text
            res = json.loads(content)
            print(res)
            if res['errorCode'] == "0":
                self.sess.get('https://login.10086.cn/registerSuccess.htm', headers=headers)
                return {"code": 0, "message": res['errorMsg']}
            else:
                continue
        return {"code": res['errorCode'], 'message': res['errorMsg']}

    def re_send(self):
        headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36',
            'Host': 'login.10086.cn',
            'Origin': 'https://login.10086.cn',
            'Referer': 'https://login.10086.cn/registerSuccess.htm'
        }
        data = {
            'type': 'sch'
        }
        for i in range(3):
            rsp = self.sess.post('https://login.10086.cn/sendemail.htm', data=data, headers=headers)
            print("重发", i, self.data['loginName'], rsp.text)
            if rsp.text == '0':
                return


class Email:
    def __init__(self):
        self.headers = {
            "Host": "bccto.me",
            "Connection": "keep-alive",
            "Cache-Control": "max-age=0",
            "Upgrade-Insecure-Requests": "1",
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/71.0.3578.98 Safari/537.36",
            "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8",
            "Accept-Encoding": "gzip, deflate, br",
            "Accept-Language": "zh-CN,zh;q=0.9,en;q=0.8,zh-TW;q=0.7,ja;q=0.6"
        }
        self.sess = requests.session()
        # + '@' + random.choice(address)
        self.username = username = gen_nonce_str(4)

    def apply(self):
        #######
        conn = redis.Redis()
        proxys = conn.smembers('un_proxy')
        if proxys:
            proxy = random.choice(list(i.decode() for i in proxys if i))
            conn = proxy or None
        else:
            conn = None
        proxy = {"http": conn}
        print(proxy)
        ####
        rsp = self.sess.get('https://bccto.me/', headers=self.headers, timeout=10, proxies=proxy)
        if '@' not in self.username:
            root = lxml.html.fromstring(rsp.text)
            eles = root.xpath('//*[@id="domainlist"]/li/a')
            address = [i.text for i in eles]
            self.username = self.username + '@' + random.choice(address)
        data = {
            'mail': self.username
        }
        print(data)
        rsp = self.sess.post('https://bccto.me/applymail', data=data, headers=self.headers, timeout=10, proxies=proxy)

        print(rsp.text)
        res = rsp.json()
        print(res)
        if res['success'] == 'false':
            return False
        return True

    def get_email(self):
        url = 'https://bccto.me/getmail'
        data2 = {'mail': self.username, 'time': 0, '_': int(time.time() * 1000)}
        #######
        conn = redis.Redis()
        proxys = conn.smembers('un_proxy')
        if proxys:
            proxy = random.choice(list(i.decode() for i in proxys if i))
            conn = proxy or None
        else:
            conn = None
        proxy = {"http": conn}
        ####
        rsp = self.sess.post(url, data=data2, headers=self.headers, timeout=10, proxies=proxy)
        res = rsp.json()
        print(res)
        if res['success']:
            if res['mail']:
                cmcc_mail = res['mail'][-1]
                u = self.username.replace("@", "(a)").replace(".", "-_-")
                fid = cmcc_mail[4]
                url = 'https://bccto.me/win/%s/%s' % (u, fid)
                print(url)
                rsp = self.sess.get(url, headers=self.headers)
                print(rsp.text)
                root = lxml.html.fromstring(rsp.text)
                ele = root.xpath('/html/body/div/div[2]/p[4]')

                return ele[0].text


def gen_nonce_str(N=4):
    return ''.join(random.choice(string.ascii_lowercase) for _ in range(N)) + ''.join(
        random.choice(string.digits) for _ in range(N))


def main():
    # username = gen_nonce_str(4) + '@' + random.choice(address)
    passwd = gen_nonce_str(4)
    email = Email()
    try:
        for _ in range(4):
            res = email.apply()
            print("--", res)
            if res:
                break
            time.sleep(2)
        if not res:
            return {"code": 1}
    except requests.exceptions.Timeout as e:
        traceback.print_exc()
        return {"cdoe": 1}
    reg = REG10086(email.username, passwd, "")

    res = reg.reg()
    print(res)
    if res['code'] == 0:
        while True:
            try:
                time.sleep(60 * 3)
                res = email.get_email()

                print(res)
                if res:
                    url = 'http://127.0.0.1:10010/reg_check'
                    link = res[:54] + res[-32:]
                    data = {"url": link}
                    rsp = requests.post(url, data=data)
                    print(rsp.text)
                    if rsp.text == '激活成功':
                        return {"code": 0, "username": email.username, 'passwd': passwd}
                    else:
                        return {"code": "23", "username": email.username, 'passwd': passwd, 'link': link}
                else:
                    reg.re_send()
            except Exception:
                traceback.print_exc()
                continue


def run():
    client = pymongo.MongoClient('mongodb://cs_user:cmcc5188@localhost:12018/cs_recharge')
    db = client.cs_recharge
    coll = db.cmcc_username
    # print(username, passwd)
    res = main()
    print("注册结果", res)
    obj = {
        "username": res['username'],
        "passwd": res['passwd'],
        "send_time": time.time()
    }
    if res['code'] == 0:
        obj['is_reg'] = '0'
    elif res['code'] == 1:
        return
    else:
        obj['link'] = res.get('link')
        obj['is_reg'] = '23'
    coll.insert_one(obj)


if __name__ == "__main__":
    pool = Pool(processes=4)
    for _ in range(600):
        pool.apply_async(run)
    pool.close()
    pool.join()
